package pl.lodz.p.browarex.ws;

import java.util.ArrayList;
import java.util.List;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import pl.lodz.p.browarex.model.AnalysiesListType;
import pl.lodz.p.browarex.model.AnalysisType;
import pl.lodz.p.browarex.model.Order;
import pl.lodz.p.browarex.model.Product;
import pl.lodz.p.browarex.model.enums.ActionType;
import pl.lodz.p.browarex.model.enums.AnalysisTypeEnum;
import pl.lodz.p.browarex.model.enums.OrderState;
import pl.lodz.p.browarex.model.enums.PackageType;
import pl.lodz.p.browarex.services.interfaces.IAnalysiesListTypeService;
import pl.lodz.p.browarex.services.interfaces.IAnalysisTypeService;
import pl.lodz.p.browarex.services.interfaces.ICustomerService;
import pl.lodz.p.browarex.services.interfaces.IOrderService;
import pl.lodz.p.browarex.services.interfaces.IProductService;
import pl.lodz.p.browarex.ws.model.AnalysisListType;
import pl.lodz.p.browarex.ws.model.AnalysisRequest;
import pl.lodz.p.browarex.ws.model.OrderResponse;
import pl.lodz.p.browarex.ws.model.ProductDistRequest;

@Component
public class Processor {

	@Autowired
	private IProductService productService;

	@Autowired
	private IOrderService orderService;
	@Autowired
	private IAnalysisTypeService analysisTypeService;
	@Autowired
	private IAnalysiesListTypeService analysiesListTypeService;
	@Autowired
	private ICustomerService customerService;

	public void processProductDistRequest(ProductDistRequest productReq) {
		Product product = new Product();
		if (productReq.getActionType().equals(ActionType.ADD.toString())) {
			product.setActionType(ActionType.ADD);
			product.setCapacity(((double) productReq.getCapacity()) / 1000);
			product.setDescription(productReq.getDescription());
			product.setPackageType(PackageType.valueOf(productReq.getBundle()));
			product.setPrice(productReq.getPrice().doubleValue());
			product.setProductID(productReq.getProductId());
			product.setProductName(productReq.getName());
			product.setQuantity(productReq.getQuantity());
			product.setType(productReq.getType());
			product.setVoltage(productReq.getVoltage());
			product.setManufacturer(productReq.getManufacturer().toString());
			productService.save(product);
		} else if (productReq.getActionType().equals(ActionType.DELETE.name())) {
			productService.delete(productService.loadByProductID(
					productReq.getProductId()).getId());
		} else if (productReq.getActionType().equals(ActionType.EDIT.name())) {
			product = productService.loadByProductID(productReq.getProductId());
			product.setActionType(ActionType.EDIT);
			product.setCapacity(((double) productReq.getCapacity()) / 1000);
			product.setDescription(productReq.getDescription());
			product.setPackageType(PackageType.valueOf(productReq.getBundle()));
			product.setPrice(productReq.getPrice().doubleValue());
			product.setProductID(productReq.getProductId());
			product.setProductName(productReq.getName());
			product.setQuantity(productReq.getQuantity());
			product.setType(productReq.getType());
			product.setVoltage(productReq.getVoltage());
			product.setManufacturer(productReq.getManufacturer().toString());
			productService.save(product);
		}
	}

	public void processOrderResponse(OrderResponse response) {
		Order order = orderService.loadByOrderID(response.getOrderId());
		// if (checkOrderStates(response, order)) {
		order.setOrderState(OrderState.valueOf(response.getOrderState()));
		order.setOrderDate(response.getOrderTimestamp().toGregorianCalendar()
				.getTime());
		orderService.save(order);
		// }
	}

	/**
	 * 
	 * @param response
	 * @param order
	 * @return return true when response orderState is higher than order
	 *         orderState
	 */
	private boolean checkOrderStates(OrderResponse response, Order order) {
		if (!response.getOrderState().equals(order.getOrderState())) {
			if (response.getOrderState().equals(OrderState.FAIL)) {
				return true;
			}
			if (response.getOrderState().equals(OrderState.REALIZED)) {
				return true;
			} else if (order.getOrderState().equals(OrderState.WAITING)) {
				return true;
			} else if (order.getOrderState().equals(OrderState.VERIFYING)
					&& response.getOrderState().equals(
							OrderState.REALIZING.getValue())) {
				return true;
			}
		}
		return false;
	}

	public void processAnalysis(AnalysisRequest request) {
		AnalysisType analysisType = analysisTypeService
				.loadByCustomerID(request.getCustomerId());
		if (analysisType == null) {
			analysisType = new AnalysisType();
		} else {
			analysisTypeService.delete(analysisType.getId());
			analysisType = new AnalysisType();
		}
		List<AnalysiesListType> list = analysisType.getAnalysies();
		if (analysisType.getAnalysies() == null) {
			list = new ArrayList<AnalysiesListType>();
		}
		for (AnalysisListType listType : request.getAnalysises()) {
			AnalysiesListType analysiesListType = new AnalysiesListType();
			if (listType.getDiscountExpiry() != null) {
				analysiesListType.setDiscountExpiry(listType
						.getDiscountExpiry().toGregorianCalendar().getTime());
			} else {
				analysiesListType.setDiscountExpiry(null);
			}

			if (listType.getDiscountValue() != null) {
				analysiesListType.setDiscountValue(Integer.parseInt(listType
						.getDiscountValue()));
			} else {
				analysiesListType.setDiscountValue(null);
			}
			analysiesListType.setProductID(listType.getProductId());
			analysiesListType.setType(AnalysisTypeEnum.valueOf(listType
					.getType().toString()));
			analysiesListType.setProduct(productService
					.loadByProductID(listType.getProductId()));
			// analysiesListTypeService.save(analysiesListType);
			list.add(analysiesListType);
		}
		analysisType.setAnalysies(list);
		analysisType.setCustomerID(request.getCustomerId());
		analysisType.setDate(request.getDate().toGregorianCalendar().getTime());
		analysisType.setCustomer(customerService.loadByCustomerID(request
				.getCustomerId()));
		analysisTypeService.save(analysisType);
	}
}
